package codec;

import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.channel.ChannelHandler;
import io.netty.channel.ChannelHandlerContext;
import io.netty.handler.codec.ByteToMessageDecoder;
import io.netty.handler.codec.LengthFieldBasedFrameDecoder;
import java.nio.ByteBuffer;
import marshall.MarshallingDecoder;
import protocol.Header;
import protocol.NettyMessage;

import java.util.HashMap;
import java.util.Map;

/**
 * 解码器
 */
public class NettyMessageDecoder extends LengthFieldBasedFrameDecoder {
    private MarshallingDecoder marshallingDecoder;

    public NettyMessageDecoder(int maxFrameLength,int lengthFieldOffset,
                               int lengthFieldLength) throws Exception {
        super(maxFrameLength,lengthFieldOffset,lengthFieldLength);
        marshallingDecoder = new MarshallingDecoder();
    }

    @Override
    protected Object decode(ChannelHandlerContext ctx, ByteBuf in) throws Exception {
        System.out.println("开始解码"+System.currentTimeMillis());
        ByteBuf frame = (ByteBuf) super.decode(ctx,in);
        if (frame == null){
            System.out.println("frame is null");
            return null;
        }
        NettyMessage message = new NettyMessage();
        Header header = new Header();
        header.setCrcCode(frame.readInt());
        header.setLength(frame.readInt());
        header.setSessionID(frame.readLong());
        header.setType(frame.readByte());
        header.setPriority(frame.readByte());

        //判断是否存在扩展消息头
        int size = frame.readInt();
        if (size > 0){
            Map<String,Object> attch = new HashMap<String, Object>(size);
            int keySize = 0;
            byte[] keyArray = null;
            String key = null;
            for (int i = 0; i < size; i++){
                keySize = frame.readInt();
                keyArray = new byte[keySize];
                frame.readBytes(keyArray);
                key = new String(keyArray,"UTF-8");
                attch.put(key,marshallingDecoder.decode(frame));
            }
            keyArray = null;
            key = null;
            header.setAttachment(attch);
        }
        if (frame.readableBytes() > 4){
            message.setBody(marshallingDecoder.decode(frame));
        }
        message.setHeader(header);
        System.out.println("解码完成");
        return message;
    }

    public static void main(String[] args) {

        ByteBuf byteBuf = Unpooled.buffer();
        byteBuf.writeBytes("加".getBytes());
        System.out.println(byteBuf.writerIndex());

    }
}
